# -*- coding:utf-8 -*- 

import gevent

__all__ = [
    'impl',
    'ret',
    'Poolable',
    'Error',
    ]

def impl(service_cls):
    bases = service_cls.__bases__
    for base in bases:
        methods = base.GetDescriptor().methods
        for method in methods:
            m = getattr(service_cls, method.name)
            bm = getattr(base, method.name)
            if m == bm:
                raise RuntimeError('service(%s)\'s method(%s) is not implemented.' \
                        % (service_cls.GetDescriptor().name, method.name))
    return service_cls

def ret(func):
    def _func(self, controller, request, done):
        result = func(self, controller, request)
        done(result)
    return _func

class Poolable(object):
    _spawn = gevent.spawn
    def full(self):
        return False

    def set_spawn(self, spawn):
        if spawn == 'default':
            self.pool = None
            self._spawn = self._spawn
        elif hasattr(spawn, 'spawn'):
            self.pool = spawn
            self._spawn = spawn.spawn
        elif isinstance(spawn, (int, long)):
            from gevent.pool import Pool
            self.pool = Pool(spawn)
            self._spawn = self.pool.spawn
        else:
            self.pool = None
            self._spawn = spawn
        if hasattr(self.pool, 'full'):
            self.full = self.pool.full

class Error(StandardError):
    pass


